package org.bookie.framework.services.impl;

import java.awt.Color;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.List;

import org.bookie.framework.services.ChartGenerator;
import org.bookie.model.Account;
import org.bookie.model.Bet;
import org.bookie.model.BetSlip;
import org.bookie.model.Outcome;
import org.bookie.model.Transaction;
import org.bookie.model.services.BetDAO;
import org.bookie.model.services.BetSlipDAO;
import org.bookie.model.services.OutcomeDAO;
import org.bookie.model.services.TransactionDAO;
import org.jfree.chart.JFreeChart;
import org.jfree.chart.axis.DateAxis;
import org.jfree.chart.axis.NumberAxis3D;
import org.jfree.chart.labels.StandardPieSectionLabelGenerator;
import org.jfree.chart.plot.PiePlot3D;
import org.jfree.chart.plot.Plot;
import org.jfree.chart.plot.XYPlot;
import org.jfree.chart.renderer.xy.DefaultXYItemRenderer;
import org.jfree.chart.renderer.xy.XYItemRenderer;
import org.jfree.data.DefaultKeyedValues;
import org.jfree.data.general.DefaultPieDataset;
import org.jfree.data.general.PieDataset;
import org.jfree.data.xy.XYSeries;
import org.jfree.data.xy.XYSeriesCollection;

public class ChartGeneratorImpl implements ChartGenerator {
	
	private TransactionDAO transactionDAO;
	private OutcomeDAO outcomeDAO;
	private BetDAO betDAO;
	private BetSlipDAO betSlipDAO;
	private static final DateFormat FORMAT = new SimpleDateFormat("d MMM yy"); 
	
	public JFreeChart createUserTransactionChart(Long id) {
		XYSeriesCollection ds = new XYSeriesCollection();
		XYSeries series = new XYSeries("Balance");
		List<Transaction> list = transactionDAO.findByUserId(id, true);
		double sum = 0;
		for(Transaction trx:list){
			sum+=trx.getAmount().doubleValue();
			series.add(new Long(trx.getDate().getTime()), new Double(sum));
		}
		ds.addSeries(series);
		
		XYSeries bsSeries = new XYSeries("Overall balance");
		sum = Account.REFILL_AMOUNT;
		List<BetSlip> betSlips = betSlipDAO.findByUserId(id);
		for(BetSlip bs:betSlips){
			if(bs.isClosed()){
				sum+=bs.getBalance();
				bsSeries.add(new Long(bs.getDate().getTime()), new Double(sum));
			}
		}
		ds.addSeries(bsSeries);
		DateAxis dateAxis = new DateAxis("Time");
		dateAxis.setDateFormatOverride(FORMAT);
		dateAxis.setVerticalTickLabels(true);
		XYItemRenderer renderer = new DefaultXYItemRenderer();
		renderer.setSeriesPaint(0, Color.ORANGE);
		XYPlot plot = new XYPlot(ds, dateAxis, new NumberAxis3D("Money"), renderer);
		return createChart("", plot, true);
	}

	public JFreeChart createBetDistributionChart(Long id){
		DefaultKeyedValues  values = new DefaultKeyedValues () ;
		Bet bet = betDAO.findById(id);
		int test = 0;
		for(Outcome outcome: bet.getOutcomes()){
			int count = outcomeDAO.countWager(outcome);
			test +=count;
			values.addValue(outcome.getLabel(),count);
		}
		if(test==0){
			values = new DefaultKeyedValues() ;
			values.addValue("No bets placed",1);
		}
		PieDataset ds = new DefaultPieDataset(values);
		PiePlot3D plot = new PiePlot3D(ds);
		plot.setStartAngle(290);
		plot.setForegroundAlpha(0.6f);
		plot.setLabelGenerator(new StandardPieSectionLabelGenerator("{0} = {1} ({2})"));
		return createChart(bet.getLabel(), plot, true);
	}
	
	private JFreeChart createChart(String title, Plot plot, boolean legend){
		JFreeChart chart = new JFreeChart(title, JFreeChart.DEFAULT_TITLE_FONT, plot, legend);
		chart.setBackgroundPaint(Color.WHITE);
		return chart;
	}
	
	public void setTransactionDAO(TransactionDAO transactionDAO) {
		this.transactionDAO = transactionDAO;
	}


	public void setOutcomeDAO(OutcomeDAO outcomeDAO) {
		this.outcomeDAO = outcomeDAO;
	}


	public void setBetDAO(BetDAO betDAO) {
		this.betDAO = betDAO;
	}

	public void setBetSlipDAO(BetSlipDAO betSlipDAO) {
		this.betSlipDAO = betSlipDAO;
	}

}
